Google Maps API Design Decisions
Understand the workflow and design considerations for the Google Maps API.
Designing an API for a mapping service is complex due to the numerous components operating under the surface. This involves several decisions, such as selecting an architectural style, a protocol, and the data formats to be used in communication between the different entities. In this lesson, we will discuss the end-to-end workflow and the design considerations for our Google Maps API.
Design overview#
The following illustration depicts a high-level architecture for Google Maps based on our functional requirements. We can divide the components involved in the architecture into the following categories:
Primary services: These services should be directly called by the different clients via an API gateway. They mainly perform the core functionalities, such as finding optimal routes, navigation directions, searching places, and so on.
Persistence layer: The persistence layer stores data such as map tiles and road data. Later, this data is useful in performing analytics to improve the overall experience of the Google Maps service.
Secondary services: These services work within the organization and help primary services to achieve their functionalities. For example, traffic and data analytics services help the route finder service to calculate the estimated time of arrival (ETA) at the destination. Also, the data analytics service analyzes the road closure situation from the different user locations and updates the maps service via a pub-sub.
Note: The map tiles represent a portion of the world map. Each map tile has a unique ID. Since sending a complete map uses unnecessary bandwidth and causes a delay, we divide the world map into tiles based on the zoom level. These tiles are kept in blob stores or served from CDNs.
Components and Services Details
Component or Service | Details |
Maps service |
|
Places service |
|
Route finder service |
|
Navigation service |
|
Pub-sub service |
|
Data analytic service |
|
Traffic service |
|
API gateway |
|
Database |
|
Workflow#
In this section, we will learn how each functional requirement is met by understanding different API calls' lifecycles spanning through different services. We refer to this process as a workflow. We have four main services: map, places, route finder, and navigation. Before the client can access any of these services, the API gateway validates the request (possibly through the API key) and routes it to the appropriate service.
Maps: The client initiates the request and sends the location to the map service. The map service processes the request and returns the map tiles associated with the zoom level and specified location. The client can fetch these tiles from the CDN, as depicted in the following illustration, and connect all these tiles to display a map.
It is also possible to store frequently used tiles on the client application. For instance, Google Maps allows mobile applications to download the map tiles of regions on the maps.
Note: The GPS of the device should be turned on to get exact map tiles. Otherwise, the server detects the user's region through the IP address and returns the map tiles of that region.
Places service: The client initiates the request to search a place by sending the user-typed address in the query parameter to the places service. The places service finds the searched place by requesting the persistence layer and returns its information to the client. This layer uses caching to reply quickly to frequently looked-up places.
Route finder: The client can find a route between the current location and the searched place or between any two points on the map. The client sends the request to the API gateway, including the source and destination locations. The API gateway then forwards the request to the route finder service (RFS). The RFS interacts with the database and can employ a number of algorithms or their variants, such as Dijkstra's, A*, Arc flags, and so on, to find optimal routes between the source and destination. Moreover, the RFS returns ETA, distance, and step-by-step directions to the user as well.
Navigation: After finding a route, the client can start navigating to the destination. The user's location is periodically sent from the client to the navigation service, and the navigation service returns the updated ETA and distance (in miles/kilometers) to the client. Further, if the user deviates from the suggested path due to blockage, the navigation service pings the route finder service through the pub-sub service to return the new route to the user.
The navigation service plays a pivotal role in providing live updates. This is because the data of different users is passed to the secondary service via the pub-sub. The secondary services determine traffic intensity on different parts of the route, based on the location data of users navigating that route.
Points to Ponder
Question 2
How does Google Maps provide live traffic updates to its users?
Since each user provides periodic location updates to Google Maps, we can batch the location of different users in an area to analyze the density of traffic. Using this information, and other parameters such as traffic sensors, historical data, input from transportation departments, user feedback, and so on, Google Maps uses predictive modeling to generate traffic patterns.
2 of 2
Design considerations#
This section will decide on the architectural patterns, HTTP version, and data formats used in our Google Maps API. Let's first define the architectural style.
Architecture styles#
Let's divide the interactions in our API service into three main categories, depending on the functional requirements:
Client-to-API gateway
API gateway-to-backend services
Client-to-navigation service
Client-to-API gateway: We use REST to get responses from search, places, and route finder services, mainly because they follow the request-response model. Our other reasons for choosing REST are as follows:
Performing read operations, which are a part of the CRUD operations
Not fetching the data from multiple services
The above-stated points naturally complement the REST architectural style. This style provides a standardized way to manage and access structured resources to fulfill user requests.
Client-to-navigation service: In this case, the client periodically sends the user's current location to the navigation service, while the navigation service sends the updated distance, time, and live updates to the clients. To deliver live updates in real-time to the clients, we use event-driven architecture here. The real-time updates require a direct connection to minimize latency. Obviously, we will first need to establish an HTTP connection to upgrade to event-driven architecture.
API gateway-to-back-end services: In this case, the request will be routed by the API gateway to the relevant service (maps, places, or router finder). GraphQL is not a suitable option here, because we're neither interacting with multiple services simultaneously, nor fetching the customized data from the different services. REST is a suitable option here, as a user does not request all services simultaneously, even if certain services communicate with each other to fulfill a user’s requirement. For example, the route-finder service is not called when the user calls the places service. However, the route finder service interacts with secondary services to come up with multiple routes to a destination.
Google employs gRPC in most of the services it offers, because Google has a lot of interconnected microservices working in tandem with each other.
We didn’t opt for gRPC in our API gateway to backend services because we only have a few services to offer in our design problem. Furthermore, for the number of services used in our design problem, REST is capable of handling the communication and scalability requirements between the API gateway and the backend services.
Communication protocol#
The data exchanged in our API includes text and images (such as maps tiles, places, directions, etc.). The user can zoom in and out on the maps at any time, so we need to download maps instantly from the server for a smooth experience. We can use both HTTP/1.1 and HTTP/2.0 for sending the multimedia data. HTTP/2.0 can be advantageous here because it is much faster than HTTP/1.1 and supports multiplexing. For connection between clients and the navigation service, we need a persistent connection to exchange data swiftly and deliver live updates in real-time. The WebSockets would be a better option, because they are lightweight and faster than HTTP/2, which adds the overhead of the header size.
Data formats#
Our Google Maps services transmit multimedia files in binary format. On the other hand, for textual data, we need human readability to integrate our services into third-party applications such as Uber. So, we use JSON for textual data as it is human-readable, compact, and easy to implement.
Points to Ponder
Question 2
Isn’t it possible for third-party applications, such as Uber, to translate data from the binary format into a human-readable format?
Binary data formats are known to be much more efficient than human-readable formats like JSON. Also, third-party applications like Uber can easily encode/decode to/from binary to other data formats.
However, using binary to exchange data with third-party applications is not a good idea, because this puts the burden of translation (from binary to other human-readable formats) on our API’s third-party applications/users.
This leads to inconvenience for a potentially large number of the users of our API. This is why it is not good practice, even if it’s plausible.
2 of 2
Summary#
The design decisions for our Google Maps service are summarized in the following table:
Design Considerations | Client-to-API Gateway | API Gateway-to-back-end | Client-to-navigation service |
Architecture style | REST | REST | Event-driven |
Data format | JSON, Binary | JSON, Binary | JSON, Binary |
HTTP version | HTTP/2 | HTTP/2 | WebSockets |
Requirements of the Google Maps API
API Model for Google Maps Service